/*
 * Copyright 2018- The Pixie Authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 * SPDX-License-Identifier: Apache-2.0
 */

syntax = "proto3";

package px.services.internal;

option go_package = "vzmgrpb";

import "github.com/gogo/protobuf/gogoproto/gogo.proto";
import "google/protobuf/empty.proto";
import "google/protobuf/timestamp.proto";
import "src/api/proto/uuidpb/uuid.proto";
import "src/shared/cvmsgspb/cvmsgs.proto";

service VZMgrService {
  rpc CreateVizierCluster(CreateVizierClusterRequest) returns (uuidpb.UUID);
  rpc GetViziersByOrg(uuidpb.UUID) returns (GetViziersByOrgResponse);
  rpc GetVizierInfo(uuidpb.UUID) returns (cvmsgspb.VizierInfo);
  rpc GetViziersByShard(GetViziersByShardRequest) returns (GetViziersByShardResponse);
  rpc GetVizierConnectionInfo(uuidpb.UUID) returns (cvmsgspb.VizierConnectionInfo);
  // Fetch vizier infos for multiple viziers.
  rpc GetVizierInfos(GetVizierInfosRequest) returns (GetVizierInfosResponse);
  // Call to acknowledge connection of a vizier.
  rpc VizierConnected(cvmsgspb.RegisterVizierRequest) returns (cvmsgspb.RegisterVizierAck);
  rpc UpdateVizierConfig(cvmsgspb.UpdateVizierConfigRequest)
      returns (cvmsgspb.UpdateVizierConfigResponse);
  // This call is made when we want to update or install a Vizier.
  rpc UpdateOrInstallVizier(cvmsgspb.UpdateOrInstallVizierRequest)
      returns (cvmsgspb.UpdateOrInstallVizierResponse);
  // Given a VizierID, get the org who owns that vizier. This should be for internal use only.
  rpc GetOrgFromVizier(uuidpb.UUID) returns (GetOrgFromVizierResponse);
}

message CreateVizierClusterRequest {
  uuidpb.UUID org_id = 1 [ (gogoproto.customname) = "OrgID" ];
  string project_name = 2;
}

message GetViziersByOrgResponse {
  repeated uuidpb.UUID vizier_ids = 1 [ (gogoproto.customname) = "VizierIDs" ];
}

// GetViziersByShardRequest gets all connected viziers within the given shard range.
message GetViziersByShardRequest {
  // The beginning of the range of Vizier shards to fetch, inclusive.
  string from_shard_id = 1 [ (gogoproto.customname) = "FromShardID" ];
  // The ending of the range of Vizier shards to fetch, also inclusive. To fetch
  // viziers for a single shard, the FromShardID and ToShardID should be the same.
  string to_shard_id = 2 [ (gogoproto.customname) = "ToShardID" ];
}

// GetViziersByShardResponse, get a information about all connected viziers in a shard.
message GetViziersByShardResponse {
  // TODO(vihang): Reconcile with VizierConnected?
  message VizierInfo {
    uuidpb.UUID vizier_id = 1 [ (gogoproto.customname) = "VizierID" ];
    uuidpb.UUID org_id = 2 [ (gogoproto.customname) = "OrgID" ];
    string k8s_uid = 4 [ (gogoproto.customname) = "K8sUID" ];
    reserved 3;  // DEPRECATED string resource_version
  }
  repeated VizierInfo viziers = 1;
}

// GetVizierInfosRequest, get information about all the given viziers.
message GetVizierInfosRequest {
  repeated uuidpb.UUID vizier_ids = 1 [ (gogoproto.customname) = "VizierIDs" ];
}

// GetVizierInfosResponse is the response to a GetVizierInfosRequest.
message GetVizierInfosResponse {
  repeated cvmsgspb.VizierInfo vizier_infos = 1;
}

//
// Deployment Key Service
//

// The service that handles deployment keys. This is a user facing service.
service VZDeploymentKeyService {
  // Create a new deployment key.
  rpc Create(CreateDeploymentKeyRequest) returns (DeploymentKey);
  // List all keys for the user/org.
  // TODO(zasgar): Update when we have RBAC.
  rpc List(ListDeploymentKeyRequest) returns (ListDeploymentKeyResponse);
  // Get the key specified by ID.
  rpc Get(GetDeploymentKeyRequest) returns (GetDeploymentKeyResponse);
  // Delete the Key specified by ID.
  rpc Delete(DeleteDeploymentKeyRequest) returns (google.protobuf.Empty);
  // Lookup the Deployment key information by the key value.
  rpc LookupDeploymentKey(LookupDeploymentKeyRequest) returns (LookupDeploymentKeyResponse);
}

// Metadata for a key that can be used to deploy a new vizier cluster.
message DeploymentKeyMetadata {
  // They ID of the key.
  uuidpb.UUID id = 1 [ (gogoproto.customname) = "ID" ];
  google.protobuf.Timestamp created_at = 3;
  // Description for the key.
  string desc = 4;
  uuidpb.UUID org_id = 5 [ (gogoproto.customname) = "OrgID" ];
  uuidpb.UUID user_id = 6 [ (gogoproto.customname) = "UserID" ];

  // 2 is reserved for the original key string.
  reserved 2;
}

// A key that can be used to deploy a new vizier cluster. This is value of the key
// is added to the X-API-KEY requests from Vizier on cloud conn.
message DeploymentKey {
  // They ID of the key.
  uuidpb.UUID id = 1 [ (gogoproto.customname) = "ID" ];
  // The value of the key.
  string key = 2;
  google.protobuf.Timestamp created_at = 3;
  // Description for the key.
  string desc = 4;
  uuidpb.UUID org_id = 5 [ (gogoproto.customname) = "OrgID" ];
  uuidpb.UUID user_id = 6 [ (gogoproto.customname) = "UserID" ];
}

// Create a deployment key.
message CreateDeploymentKeyRequest {
  // Description for the key.
  string desc = 1;
  uuidpb.UUID org_id = 2 [ (gogoproto.customname) = "OrgID" ];
  uuidpb.UUID user_id = 3 [ (gogoproto.customname) = "UserID" ];
}

message ListDeploymentKeyRequest {
  uuidpb.UUID org_id = 1 [ (gogoproto.customname) = "OrgID" ];
}

message ListDeploymentKeyResponse {
  repeated DeploymentKeyMetadata keys = 1;
}

message GetDeploymentKeyRequest {
  uuidpb.UUID id = 1 [ (gogoproto.customname) = "ID" ];
  uuidpb.UUID org_id = 2 [ (gogoproto.customname) = "OrgID" ];
}

message GetDeploymentKeyResponse {
  DeploymentKey key = 1;
}

message DeleteDeploymentKeyRequest {
  uuidpb.UUID id = 1 [ (gogoproto.customname) = "ID" ];
  uuidpb.UUID org_id = 2 [ (gogoproto.customname) = "OrgID" ];
}

message LookupDeploymentKeyRequest {
  string key = 1;
}

message LookupDeploymentKeyResponse {
  DeploymentKey key = 1;
}

//
// Deployment Service
//

// The service that deployment and registration of Viziers. Its primary
// consumer is Vizier through Vzconn.
service VZDeploymentService {
  rpc RegisterVizierDeployment(RegisterVizierDeploymentRequest)
      returns (RegisterVizierDeploymentResponse);
}

message RegisterVizierDeploymentRequest {
  // The UID of the K8s cluster. This is typically the UI of the kube-system namespace.
  // We assume this is globally unique.
  string k8s_cluster_uid = 1 [ (gogoproto.customname) = "K8sClusterUID" ];
  // The deployment key that will be use to register this vizier. The org/user it's registered
  // to will be determined by this key.
  string deployment_key = 2;
  // The name of the cluster. If none is specified, a random name will be generated.
  string k8s_cluster_name = 3 [ (gogoproto.customname) = "K8sClusterName" ];
  reserved 4;  // DEPRECATED
}

// RegisterVizierDeploymentResponse returns the registration status. It either will include the
// assigned vizier_id or a GRPC error will be returned.
message RegisterVizierDeploymentResponse {
  // The ID for this Vizier.
  uuidpb.UUID vizier_id = 1 [ (gogoproto.customname) = "VizierID" ];
  // The name for this Vizier.
  string vizier_name = 2;
}

// GetOrgFromVizierResponse returns which org the given Vizier belongs to.
message GetOrgFromVizierResponse {
  // The org which owns the Vizier.
  uuidpb.UUID org_id = 1 [ (gogoproto.customname) = "OrgID" ];
}
